package com.cmc.cloud.cmclink.doc.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.lock.annotation.Lock4j;
import com.cmc.cloud.cmclink.doc.constants.errorconstant.SetupWeightLimitedErrorCodeConstants;
import com.cmc.cloud.cmclink.doc.vo.setupweightlimitedvo.SetupWeightLimitedBaseVO;
import com.cmc.cloud.cmclink.doc.vo.setupweightlimitedvo.SetupWeightLimitedCreateReqVO;
import com.cmc.cloud.cmclink.doc.vo.setupweightlimitedvo.SetupWeightLimitedPageReqVO;
import com.cmc.cloud.cmclink.doc.vo.setupweightlimitedvo.SetupWeightLimitedUpdateReqVO;
import com.cmes.framework.mybatis.core.query.LambdaQueryWrapperX;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;

import org.springframework.transaction.annotation.Transactional;
import org.springframework.validation.annotation.Validated;


import com.cmes.framework.common.pojo.PageResult;
import com.cmes.framework.common.exception.util.ServiceExceptionUtil;

import java.util.*;

import com.cmc.cloud.cmclink.doc.service.SetupWeightLimitedService;
import com.cmc.cloud.cmclink.doc.entity.SetupWeightLimitedDO;
import com.cmc.cloud.cmclink.doc.mapper.SetupWeightLimitedMapper;


/**
 * 限重维护 Service 实现类
 *
 * @author 招商轮船-管理员
 */
@Service
@Validated
public class SetupWeightLimitedServiceImpl implements SetupWeightLimitedService {

    @Resource
    private SetupWeightLimitedMapper setupWeightLimitedMapper;

    @Override
    @Transactional(rollbackFor = Exception.class)
    @Lock4j(name = "setupWeightLimitedUnique", keys = {"#createReqVO.getLaneCode", "#createReqVO.getVesselCode", "#createReqVO.getVesselOperatorCode"
            , "#createReqVO.getPodCode", "#createReqVO.getPolCode", "#createReqVO.getCntrSize", "#createReqVO.getCntrType"})
    public void createSetupWeightLimited(SetupWeightLimitedCreateReqVO createReqVO) {
        // 插入
        validateUnique(createReqVO, null);
        SetupWeightLimitedDO setupWeightLimited = BeanUtil.copyProperties(createReqVO, SetupWeightLimitedDO.class);
        setupWeightLimitedMapper.insert(setupWeightLimited);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @Lock4j(name = "setupWeightLimitedUnique", keys = {"#updateReqVO.getLaneCode", "#updateReqVO.getVesselCode", "#updateReqVO.getVesselOperatorCode"
            , "#updateReqVO.getPodCode", "#updateReqVO.getPolCode", "#updateReqVO.getCntrSize", "#updateReqVO.getCntrType"})
    public void updateSetupWeightLimited(SetupWeightLimitedUpdateReqVO updateReqVO) {
        // 校验存在
        validateSetupWeightLimitedExists(updateReqVO.getId());
        validateUnique(updateReqVO, updateReqVO.getId());
        // 更新
        SetupWeightLimitedDO updateObj = BeanUtil.copyProperties(updateReqVO, SetupWeightLimitedDO.class);
        setupWeightLimitedMapper.updateById(updateObj);
    }

    @Override
    public void deleteSetupWeightLimited(Long id) {
        // 校验存在
        validateSetupWeightLimitedExists(id);
        // 删除
        setupWeightLimitedMapper.deleteById(id);
    }

    private void validateSetupWeightLimitedExists(Long id) {
        if (setupWeightLimitedMapper.selectById(id) == null) {
            throw ServiceExceptionUtil.exception(SetupWeightLimitedErrorCodeConstants.SETUP_WEIGHT_LIMITED_NOT_EXISTS);
        }
    }

    private void validateUnique(SetupWeightLimitedBaseVO vo, Long id) {
        LambdaQueryWrapperX<SetupWeightLimitedDO> queryWrapperX = new LambdaQueryWrapperX<SetupWeightLimitedDO>()
                .eqIfPresent(SetupWeightLimitedDO::getLaneCode, vo.getLaneCode())
                .eqIfPresent(SetupWeightLimitedDO::getVesselCode, vo.getVesselCode())
                .eqIfPresent(SetupWeightLimitedDO::getVesselOperatorCode, vo.getVesselOperatorCode())
                .eqIfPresent(SetupWeightLimitedDO::getPodCode, vo.getPodCode())
                .eqIfPresent(SetupWeightLimitedDO::getPolCode, vo.getPolCode())
                .eqIfPresent(SetupWeightLimitedDO::getCntrSize, vo.getCntrSize())
                .eqIfPresent(SetupWeightLimitedDO::getCntrType, vo.getCntrType());
        if (id != null) {
            queryWrapperX.ne(SetupWeightLimitedDO::getId, id);
        }
        if (setupWeightLimitedMapper.selectCount(queryWrapperX) != 0L) {
            throw ServiceExceptionUtil.exception(SetupWeightLimitedErrorCodeConstants.SETUP_WEIGHT_LIMITED_EXISTED);
        }
    }

    @Override
    public SetupWeightLimitedDO getSetupWeightLimited(Long id) {
        return setupWeightLimitedMapper.selectById(id);
    }

    @Override
    public List<SetupWeightLimitedDO> getSetupWeightLimitedList(Collection<Long> ids) {
        return setupWeightLimitedMapper.selectBatchIds(ids);
    }

    @Override
    public PageResult<SetupWeightLimitedDO> getSetupWeightLimitedPage(SetupWeightLimitedPageReqVO reqVO) {
        LambdaQueryWrapperX<SetupWeightLimitedDO> queryWrapperX = new LambdaQueryWrapperX<>();
        queryWrapperX.eqIfPresent(SetupWeightLimitedDO::getLaneCode, reqVO.getLaneCode())
                .eqIfPresent(SetupWeightLimitedDO::getVesselCode, reqVO.getVesselCode())
                .eqIfPresent(SetupWeightLimitedDO::getVesselOperatorCode, reqVO.getVesselOperatorCode())
                .eqIfPresent(SetupWeightLimitedDO::getPodCode, reqVO.getPodCode())
                .eqIfPresent(SetupWeightLimitedDO::getPolCode, reqVO.getPolCode());
        return setupWeightLimitedMapper.selectPage(reqVO, queryWrapperX);
    }
}
